/**
 * 机器翻译2.0(niutrans) WebAPI 接口调用示例
 * 运行前：请先填写Appid、APIKey、APISecret
 * 运行方法：直接运行 main() 即可
 * 结果： 控制台输出结果信息
 *
 * 1.接口文档（必看）：https://www.xfyun.cn/doc/nlp/niutrans/API.html
 * 2.错误码链接：https://www.xfyun.cn/document/error-code （错误码code为5位数字）
 * 3.个性化翻译术语自定义：
 * ***登陆开放平台 https://www.xfyun.cn/
 * ***在控制台--机器翻译(niutrans)--自定义翻译处
 * ***上传自定义翻译文件（打开上传或更新窗口，可下载示例文件）
 * @author iflytek
 */
import CryptoJS from "crypto-js";
import { readFileSync, writeFileSync } from "node:fs";
import { I18nConfig, ILogger } from "../types";

// 系统配置
const config = {
  // 请求地址
  hostUrl: "https://ntrans.xfyun.cn/v2/ots",
  host: "ntrans.xfyun.cn",
  //在控制台-我的应用-机器翻译获取
  uri: "/v2/ots",
};

let transVar = {
  from: "cn", //源语种
  to: "en", //目标语种
};

// 生成请求body
function getPostBody(text: string, from: string, to: string, appid: string) {
  const digestObj = {
    //填充common
    common: {
      app_id: appid,
    },
    //填充business
    business: {
      from: from,
      to: to,
    },
    //填充data
    data: {
      text: CryptoJS.enc.Base64.stringify(CryptoJS.enc.Utf8.parse(text)),
    },
  };
  return digestObj;
}

// 请求获取请求体签名
function getDigest(body: Record<string, any>) {
  return (
    "SHA-256=" +
    CryptoJS.enc.Base64.stringify(CryptoJS.SHA256(JSON.stringify(body)))
  );
}

// 鉴权签名
function getAuthStr(date: string, digest: string, CONFIG: I18nConfig) {
  let signatureOrigin = `host: ${config.host}\ndate: ${date}\nPOST ${config.uri} HTTP/1.1\ndigest: ${digest}`;
  let signatureSha = CryptoJS.HmacSHA256(signatureOrigin, CONFIG.apiSecret);
  let signature = CryptoJS.enc.Base64.stringify(signatureSha);
  let authorizationOrigin = `api_key="${CONFIG.apiKey}", algorithm="hmac-sha256", headers="host date request-line digest", signature="${signature}"`;
  return authorizationOrigin;
}

// 发送请求
const translate = async (text: string, CONFIG: I18nConfig, logger: ILogger) => {
  // 获取当前时间 RFC1123格式
  let date = new Date().toUTCString();
  let postBody = getPostBody(text, transVar.from, transVar.to, CONFIG.appid);
  let digest = getDigest(postBody);

  let options = {
    url: config.hostUrl,
    method: "POST",
    headers: {
      "Content-Type": "application/json",
      Accept: "application/json,version=1.0",
      Host: config.host,
      Date: date,
      Digest: digest,
      Authorization: getAuthStr(date, digest, CONFIG),
    },
    // json: true,
    body: JSON.stringify(postBody),
  };
  logger("正在翻译:" + text, "info");
  const res = (await fetch(config.hostUrl, options).catch((err) => {
    console.error("err", err);
  })) as Response;
  const resJson = (await res.json()) as { data: any };
  return resJson?.data.result?.trans_result?.dst;
};
export const batchTranslate = async (CONFIG: I18nConfig, logger: ILogger) => {
  if (!CONFIG.apiKey || !CONFIG.apiSecret || !CONFIG.appid) {
    logger("请先配置apiKey、apiSecret、appid", "error");
    return;
  }
  const fileContent = JSON.parse(readFileSync(CONFIG.LANG_FILE, "utf-8"));
  const translated = JSON.parse(readFileSync(CONFIG.TRANS_FILE, "utf-8"));
  const keys = Object.keys(fileContent);
  while (keys.length) {
    const key = keys.shift();
    if (key && !translated[key]) {
      try {
        translated[key] = await translate(fileContent[key], CONFIG, logger);
      } catch (error) {
        logger(JSON.stringify(error), "error");
      }
    }
  }
  writeFileSync(CONFIG.TRANS_FILE, JSON.stringify(translated, null, 2));
  logger(`翻译完毕`, "info");
};
